/**
 * 小程序模版删除队列管理器
 * 用于处理批量删除模版的并发控制,避免触发微信API的并发限制
 */
const axios = require('axios');
const { v4: uuidv4 } = require('uuid');

class TemplateDeleteQueue {
  constructor() {
    // 存储所有删除任务
    this.tasks = new Map();

    // 删除队列
    this.queue = [];

    // 是否正在处理
    this.processing = false;

    // 并发控制: 每次只处理1个请求
    this.concurrency = 1;

    // 请求间隔时间(毫秒)
    // 微信API限流策略: 观察到前5个成功,说明可能是"短时间窗口内最多5个请求"
    // 使用10秒间隔,确保每个请求都在新的时间窗口
    this.requestInterval = 10000; // 10秒

    // 成功请求计数器
    this.successCount = 0;

    // 每5个请求后额外等待(防止时间窗口限流)
    this.batchSize = 5;
    this.batchWaitTime = 30000; // 30秒
  }

  /**
   * 创建批量删除任务
   * @param {string} accessToken - component_access_token
   * @param {Array} templates - 要删除的模版列表
   * @returns {string} taskId - 任务ID
   */
  createTask(accessToken, templates) {
    const taskId = uuidv4();

    const task = {
      taskId,
      accessToken,
      templates: templates.map(t => ({
        template_id: t.template_id,
        user_version: t.user_version,
        status: 'pending', // pending, deleting, success, failed
        error: null
      })),
      status: 'pending', // pending, processing, completed
      createdAt: new Date(),
      updatedAt: new Date(),
      progress: {
        total: templates.length,
        success: 0,
        failed: 0,
        pending: templates.length
      }
    };

    this.tasks.set(taskId, task);
    this.queue.push(taskId);

    // 启动处理
    this.startProcessing();

    return taskId;
  }

  /**
   * 获取任务状态
   * @param {string} taskId - 任务ID
   * @returns {Object} task - 任务对象
   */
  getTask(taskId) {
    return this.tasks.get(taskId);
  }

  /**
   * 开始处理队列
   */
  async startProcessing() {
    if (this.processing) return;

    this.processing = true;

    while (this.queue.length > 0) {
      const taskId = this.queue.shift();
      const task = this.tasks.get(taskId);

      if (!task) continue;

      task.status = 'processing';
      task.updatedAt = new Date();

      console.log(`开始处理删除任务: ${taskId}, 共 ${task.templates.length} 个模版`);

      // 逐个删除模版
      for (let i = 0; i < task.templates.length; i++) {
        const template = task.templates[i];

        template.status = 'deleting';
        task.updatedAt = new Date();

        try {
          // 调用微信API删除模版
          const response = await axios.post(
            `https://api.weixin.qq.com/wxa/deletetemplate?access_token=${task.accessToken}`,
            {
              template_id: template.template_id
            },
            {
              headers: {
                'Content-Type': 'application/json'
              }
            }
          );

          if (response.data.errcode === 0) {
            template.status = 'success';
            task.progress.success++;
            this.successCount++;
            console.log(`✅ 删除模版成功: ${template.template_id} (成功计数: ${this.successCount})`);
          } else {
            template.status = 'failed';
            template.error = response.data.errmsg || '未知错误';
            task.progress.failed++;
            console.error(`❌ 删除模版失败: ${template.template_id}, ${template.error}`);
          }
        } catch (error) {
          template.status = 'failed';
          template.error = error.response?.data?.errmsg || error.message;
          task.progress.failed++;
          console.error(`❌ 删除模版异常: ${template.template_id}`, error.message);
        }

        task.progress.pending--;
        task.updatedAt = new Date();

        // 请求间隔,避免触发并发限制
        if (i < task.templates.length - 1) {
          // 每5个成功请求后,额外等待30秒
          if (this.successCount > 0 && this.successCount % this.batchSize === 0) {
            console.log(`⏸️  已成功删除 ${this.successCount} 个模版,等待 ${this.batchWaitTime / 1000} 秒避免限流...`);
            await this.sleep(this.batchWaitTime);
          } else {
            await this.sleep(this.requestInterval);
          }
        }
      }

      // 重置成功计数器
      this.successCount = 0;

      task.status = 'completed';
      task.updatedAt = new Date();

      console.log(`✅ 删除任务完成: ${taskId}, 成功 ${task.progress.success} 个, 失败 ${task.progress.failed} 个`);
    }

    this.processing = false;
  }

  /**
   * 延迟函数
   * @param {number} ms - 延迟时间(毫秒)
   */
  sleep(ms) {
    return new Promise(resolve => setTimeout(resolve, ms));
  }

  /**
   * 清理过期任务(保留最近1小时的任务)
   */
  cleanupOldTasks() {
    const oneHourAgo = new Date(Date.now() - 60 * 60 * 1000);

    for (const [taskId, task] of this.tasks.entries()) {
      if (task.status === 'completed' && task.updatedAt < oneHourAgo) {
        this.tasks.delete(taskId);
        console.log(`清理过期任务: ${taskId}`);
      }
    }
  }

  /**
   * 获取所有任务列表
   * @returns {Array} tasks
   */
  getAllTasks() {
    return Array.from(this.tasks.values());
  }
}

// 创建单例
const templateDeleteQueue = new TemplateDeleteQueue();

// 定期清理过期任务(每小时)
setInterval(() => {
  templateDeleteQueue.cleanupOldTasks();
}, 60 * 60 * 1000);

module.exports = templateDeleteQueue;
